package com.gitee.xcfyl.simplehttpserver.server;

import com.gitee.xcfyl.simplehttpserver.config.ServerConfig;
import com.gitee.xcfyl.simplehttpserver.io.HttpRequest;
import com.gitee.xcfyl.simplehttpserver.io.HttpResponse;
import com.gitee.xcfyl.simplehttpserver.servlet.HttpServlet;
import lombok.extern.slf4j.Slf4j;

import java.io.InputStream;
import java.io.OutputStream;
import java.net.ServerSocket;
import java.net.Socket;
import java.util.concurrent.LinkedBlockingQueue;
import java.util.concurrent.ThreadPoolExecutor;
import java.util.concurrent.TimeUnit;

/**
 * 简单Http请求服务器
 *
 * @author 西城风雨楼
 */
@Slf4j
public class SimpleHttpServer {
    /**
     * 创建线程池
     */
    private static final ThreadPoolExecutor EXECUTOR = new ThreadPoolExecutor(10,
            10,
            0L,
            TimeUnit.MILLISECONDS,
            new LinkedBlockingQueue<>(1024),
            new ThreadPoolExecutor.AbortPolicy());
    /**
     * 保存服务端的配置信息
     */
    private ServerConfig serverConfig;

    private volatile boolean stop;

    /**
     * 开启服务器
     */
    public void startServer() throws Exception {
        init();
        if (log.isDebugEnabled()) {
            log.debug("服务器初始化完成，监听端口{}", serverConfig.getServerPort());
        }
        try (ServerSocket serverSocket = new ServerSocket(serverConfig.getServerPort())) {
            while (!stop) {
                Socket client = serverSocket.accept();
                if (log.isDebugEnabled()) {
                    log.debug("新的客户端连接: {}", client);
                }
                if (log.isDebugEnabled()) {
                    log.debug("开始处理请求");
                }
                process(client);
            }
        }
        if (log.isDebugEnabled()) {
            log.debug("服务器运行结束");
        }
    }

    public void stop() {
        stop = true;
    }

    private void process(Socket client) {
        log.debug("开启新的请求线程");
        log.debug("处理处理...");
        InputStream inputStream = null;
        OutputStream outputStream = null;
        try {
            log.debug("测试测试");
            inputStream = client.getInputStream();
            outputStream = client.getOutputStream();
            log.debug("测试测试2");
            HttpRequest req = new HttpRequest(inputStream);
            HttpResponse res = new HttpResponse(outputStream);

            // 获取当前请求的路径
            String url = req.getUrl();
            if (log.isDebugEnabled()) {
                log.debug("请求的url为: {}", url);
            }
            if (serverConfig.containsUrl(url)) {
                HttpServlet servlet = serverConfig.getServletByUrl(url);
                if (log.isDebugEnabled()) {
                    log.debug("开始响应请求，请求被分发到{}", servlet);
                }
                servlet.service(req, res);
            } else {
                res.write("404 - Not Found");
            }
        } catch (Exception e) {
            e.printStackTrace();
        } finally {
            try {
                if (outputStream != null) {
                    outputStream.flush();
                    outputStream.close();
                }
                if (inputStream != null) {
                    inputStream.close();
                }
                if (client != null) {
                    client.close();
                }
            } catch (Exception e) {
                e.printStackTrace();
            }
        }
    }


    /**
     * 初始化httpserver
     */
    private void init() {
        // 读取并加载配置
        serverConfig = ServerConfig.getInstance();
    }

    public static void main(String[] args) throws Exception {
        new SimpleHttpServer().startServer();
    }
}
